Transactions and batch queries {prisma}
TODO
Transactions and batch queries 를 주의깊게 읽은 후 애그리거트가 지켜야 하는 트랜잭션 경계를 프리즈마를 사용하여 어떻게 달성할 수 있는지 알아봅시다.
Prisma가 우리 몰래 트랜잭션을 사용하는 경우
- Bulk Operations
createMany
createManyAndReturn
updateMany
updateManyAndReturn
deleteMany
- Nested Writes
Can I use nested writes with bulk operations?
No - neither updateMany
nor deleteMany
currently supports nested writes. For example, you cannot delete multiple teams and all of their members (a cascading delete):
await prisma.team.deleteMany({
where: {
id: {
in: [2, 99, 2, 11],
},
},
data: {
members: {}, // Cannot access members here
},
})
우리가 명시적으로 $transaction([])
API를 사용하는 경우
UseCase: 여러 테이블에 걸친 Delete Operation
const id = 9 // User to be deleted
const deletePosts = prisma.post.deleteMany({
where: {
userId: id,
},
})
const deleteMessages = prisma.privateMessage.deleteMany({
where: {
userId: id,
},
})
const deleteUser = prisma.user.delete({
where: {
id: id,
},
})
await prisma.$transaction([deletePosts, deleteMessages, deleteUser]) // Operations succeed or fail together
UseCase: pre-computed ID를 사용하고자 하는 경우
문서에서는 UUID를 사용하였으나, 내가 알기론 ObjectId도 애플리케이션 단에서 생성이 가능하다고 들었는데, 굳이 Nested Write를 사용하지 않고도 독립적인 오퍼레이션들로 분리한 다음 하나의 트랜잭션으로 실행하는 것도 적극적으로 도입해볼 수 있겠다.
import { v4 } from 'uuid'
const teamID = v4()
const userID = v4()
await prisma.$transaction([
prisma.user.create({
data: {
id: userID,
email: 'alice@prisma.io',
team: {
id: teamID,
},
},
}),
prisma.team.create({
data: {
id: teamID,
name: 'Aurora Adventures',
},
}),
])